fix(spanner): preserve all async cache updates#12740
Conversation
There was a problem hiding this comment.
Code Review
This pull request refactors the ChannelFinder class to support queuing multiple asynchronous cache updates using a ConcurrentLinkedQueue, replacing the previous logic that only retained the latest pending update. It introduces helper methods to filter out non-material updates and improves the handling of database ID transitions to prevent unnecessary cache clears. The update draining mechanism was updated to ensure all queued tasks are processed, and awaitPendingUpdates was adjusted for better synchronization in tests. New unit tests were added to verify that updates are processed in order without being dropped and to validate edge cases for database ID changes. I have no feedback to provide as there were no review comments to assess.
Summary
This change fixes cache updates being missed after cache application moved off the request hot path. It replaces the lossy async updater with a lossless queue, skips truly empty async cache updates, moves endpoint lifecycle reconciliation off the cache-apply critical path
Problem
After moving cache application off the request hot path, cache updates could either be lost or applied too slowly. In production this showed up as:
We also observed that a large number of responses carried a
cache_updatefield that was present but effectively empty, which added queue pressure without changing routing state.Root Cause
There were a few separate issues:
databaseId=0updates could clear an already initialized finder state even when they did not carry meaningful cache contentsWhat This PR Changes
Result
Based on production logs after the fix:
This indicates the main issue was queue pressure from lossy handling and empty/no-op updates, not slow cache map mutation itself.